#include "epdfunc.h"

#include "app_drv_fifo/app_drv_fifo.h"

app_drv_fifo_t epd_temp_fifo;
static uint8_t epd_temp_fifo_buffer[512] = {0};
static uint8_t epd_temp_buffer[127] = {0};

uint32_t display_buffer_size;
// #define EPD_COLOR 2
uint8_t *image_buffer_black;
String return_log;
uint32_t image_length = 0;
uint32_t image_total_length = 0;
static uint8_t image_checknum;
uint8_t imagecolor;
uint8_t epd_write_flag;

int rotation = 0;

extern uint8_t display_flag;
static uint8_t *image_buffer;
static uint8_t *image_red_buffer;
// static uint8_t *image_buffer_temp;
// static uint8_t *image_red_buffer_temp;

static uint8_t *image_buffer_temp;
static uint32_t image_buffer_temp_size = 256; // 512;

uint8_t greyscale;

/**
 * @brief 获取数据的校验和
 *
 * @return UINT8
 */
uint8_t checksum(uint8_t *record, uint32_t len)
{
    uint8_t sum = 0x00;
    uint32_t i;
    for (i = 0; i < len; i++)
    {
        sum += record[i];
        // Serial.printf("%d,%d\n", i, sum);
    }
    // sum %= 0XFF;
    return sum;
}

/**
 * @brief  Convert hex_array  to number.
 * @param  HexStrArray: pointer to the hex  array
 * @param  len: length of the hex .
 * @retval number;
 */
int HexArray2Num(uint8_t *HexArray, int len)
{
    int j = 0;
    uint32_t num = 0;
    for (int i = 0; i < len; i++)
    {
        num = (num << 8) + HexArray[i];
        // PRINT_RAW( "%04x %02x\n", num, HexArray[i]);
    }
    return num;
}

void eink_inti(uint8_t lut_type)
{
    // display_buffer_size = EPD_HEIGHT * EPD_WIDTH / 8;
    DEV_Module_Init();
    // delay(5);
    PRINT_DEBUG("e-Paper Init and Clear...\r\n");
#if defined(EPD154C1)
    // EPD_1IN54_Init(EPD_1IN54_FULL);
    // delay(100);
    EPD_1IN54_Grey_fullpart(EPD_1IN54_Grey_FULL);
#elif defined(EPD154Z91)
    EPD_1IN54B_Z91_Init();
#elif defined(EPD154Z17)
    EPD_1IN54B_Z17_Init();
#elif defined(EPD290Z94)
    // EPD_2IN9B_Z94_Init();
    EPD_2IN9B_Z94_Grey_Init(lut_type);
#elif defined(EPD266Z90)
    EPD_2IN66B_Z90_Grey_Init(lut_type);
#elif defined(EPD420Z99)
    EPD_4IN2B_Z99_Init(lut_type);
#elif defined(EPD583Z83)
    EPD_5IN83B_Z83_Init(lut_type);
#elif defined(EPD266H850)
    EPD_2IN66B_H850_Grey_Init(lut_type);
#elif defined(EPD154A05)
    EPD_1IN54_A05_Init(EPD_1IN54_A05_FULL);
#elif defined(EPD270T91)
    EPD_2IN7_T91_Init();
#endif
    // EPD_1IN54_Clear();

    // image_buffer_black = (uint8_t *)malloc(display_buffer_size);
    // memset(image_buffer_black, 0xFF, display_buffer_size);
}

void epd_data_write(uint8_t color, uint8_t *Image_Data, uint32_t index, uint32_t length)
{
#if defined(EPD154C1)
    EPD_1IN54_Grey_Data_Write(color, Image_Data, index, length);
#elif defined(EPD154Z91)
    EPD_1IN54B_Z91_Data_Write(color, Image_Data, index, length);
#elif defined(EPD154Z17)
    EPD_1IN54B_Z17_Data_Write(color, Image_Data, index, length);
#elif defined(EPD290Z94)
    // EPD_2IN9B_Z94_Data_Write(color, Image_Data, index, length);
    EPD_2IN9B_Z94_Grey_Data_Write(color, Image_Data, index, length);
#elif defined(EPD266Z90)
    // EPD_2IN9B_Z94_Data_Write(color, Image_Data, index, length);
    EPD_2IN66B_Z90_Grey_Data_Write(color, Image_Data, index, length);
#elif defined(EPD420Z99)
    EPD_4IN2B_Z99_Data_Write(color, Image_Data, index, length);
#elif defined(EPD583Z83)
    EPD_5IN83B_Z83_Data_Write(color, Image_Data, index, length);
#elif defined(EPD266H850)
    EPD_2IN66B_H850_Grey_Data_Write(color, Image_Data, index, length);
#elif defined(EPD154A05)
    EPD_1IN54_A05_Data_Write(color, Image_Data, index, length);
#elif defined(EPD270T91)
    EPD_2IN7_T91_Data_Write(color, Image_Data, index, length);
#endif
}

// uint32_t run_length_decoding(uint8_t *data, uint8_t epd_write_flag, uint16_t data_size, uint8_t color= 0);
uint32_t run_length_decoding(uint8_t *data, uint16_t data_size, uint8_t color = 0) // advanced
{
    PRINT_DEBUG("run_length_decoding mode....\n");

    if (image_length == 0)
    {
        app_drv_fifo_init(&epd_temp_fifo, epd_temp_fifo_buffer, sizeof(epd_temp_fifo_buffer));
    }
    int imagedata_index = 0;
    app_drv_fifo_write(&epd_temp_fifo, data, &data_size);
    // PRINT_DEBUG("%d,%d,%d,%d....\n",epd_temp_ringbuffer.ringbuffer_size,epd_temp_ringbuffer.length,epd_temp_ringbuffer.start_pos,epd_temp_ringbuffer.end_pos);
    // PRINT_DEBUG("%d....\n", app_drv_fifo_length(&epd_temp_fifo));
    // for (int i = 0; i < data_size; i = i + 2)
    while (app_drv_fifo_length(&epd_temp_fifo) > 0)
    {
        uint8_t read_temp[1];
        uint16_t read_temp_length = 1;
        uint8_t read_temp2[127];
        uint16_t read_temp2_length = 0;
        app_drv_fifo_read(&epd_temp_fifo, read_temp, &read_temp_length);
        // memset(epd_temp_buffer, 0, sizeof(epd_temp_buffer)/sizeof(epd_temp_buffer[0]));
        if (read_temp[0] > 0x7F) // 1 time mode
        {
            if (app_drv_fifo_length(&epd_temp_fifo) < (read_temp[0] & 0x7F))
            {
                read_temp2_length = app_drv_fifo_length(&epd_temp_fifo);
                app_drv_fifo_read(&epd_temp_fifo, read_temp2, &read_temp2_length);
                app_drv_fifo_write(&epd_temp_fifo, read_temp, &read_temp_length);
                app_drv_fifo_write(&epd_temp_fifo, read_temp2, &read_temp2_length);
                PRINT_DEBUG("reserve to next data....\n");
                break;
            }
            else
            {
                // PRINT_DEBUG(">>>>???....\n");
                uint8_t times = read_temp[0] & 0x7F;
                read_temp2_length = times;
                app_drv_fifo_read(&epd_temp_fifo, read_temp2, &read_temp2_length);
                if (epd_write_flag == 1)
                // if (0)
                {
                    memcpy(epd_temp_buffer, read_temp2, times);
                    // epd_data_write(imagecolor, epd_temp_buffer, image_length, times);//?????
                    epd_data_write(imagecolor, epd_temp_buffer, image_length+imagedata_index, times);//?????
                    // PRINT_INFO("checksum0:%x....\n",image_checknum);
                    // image_checknum += checksum(epd_temp_buffer, times);
                    // PRINT_INFO("checksum:%x....\n",image_checknum);
                }
                else
                {
                    if (color)
                        memcpy(image_red_buffer + image_length + imagedata_index, read_temp2, times);
                    else
                        memcpy(image_buffer + image_length + imagedata_index, read_temp2, times);
                }

                imagedata_index += times;
            }
        }
        else // repeate mode
        {
            if (app_drv_fifo_length(&epd_temp_fifo) == 0)
            {
                //  PRINT_DEBUG("%d....\n",app_drv_fifo_length(&epd_temp_fifo));
                app_drv_fifo_write(&epd_temp_fifo, read_temp, &read_temp_length);
                PRINT_DEBUG("reserve   next data....\n");
                break;
            }
            else
            {
                uint8_t read_temp2[1];
                uint16_t read_temp2_length = 1;
                app_drv_fifo_read(&epd_temp_fifo, read_temp2, &read_temp2_length);
                if (epd_write_flag == 1)
                // if (0)
                {

                    // PRINT_DEBUG(">>>>....\n");
                    memset(epd_temp_buffer, read_temp2[0], read_temp[0]);
                    // epd_data_write(imagecolor, epd_temp_buffer, image_length, read_temp[0]);//??????
                    epd_data_write(imagecolor, epd_temp_buffer, image_length+imagedata_index, read_temp[0]);//??????
                    // PRINT_INFO("checksum0:%x....\n",image_checknum);
                    // image_checknum += checksum(epd_temp_buffer, read_temp[0]);
                    // PRINT_INFO("checksum:%x....\n", image_checknum);
                }
                else
                {
                    // PRINT_DEBUG("!!!!....\n");
                    if (color)

                    {
                        memset(image_red_buffer + image_length + imagedata_index, read_temp2[0], read_temp[0]);
                        // PRINT_DEBUG("@@@@@@@@....\n");
                    }

                    else
                        memset(image_buffer + image_length + imagedata_index, read_temp2[0], read_temp[0]);
                }
                imagedata_index += read_temp[0];
            }
        }
    }
    uint32_t imagedata_add_size = imagedata_index;
    PRINT_DEBUG("imagedata_add_size:%d\n", imagedata_add_size);
    return imagedata_add_size;
}

void EpdCmdWrite(uint8_t *data, int data_length)
{

    // PRINT_DEBUG("*********\n");

    if (data_length < 20)
    {
        for (int i = 0; i < data_length; i++)
        {
            PRINT_RAW("%02x ", data[i]);
        }
        PRINT_RAW("\n");
    }

    // uint32_t data_length = HexArray2Num(data + 2, 3);
    // PRINT_DEBUG("data_length:%d\n", data_length);
    // if (data_length != (length))
    // {
    //     PRINT_ERROR("data_length error!!!\n");
    //     return;
    // }
    // if (data[data_length - 1] != checksum(data, length - 1))
    // {
    //     PRINT_ERROR("check_num error!!!\n");
    //     return;
    // }

    switch (data[0])
    {
#if EPD_COLOR == 2
    case 0x20: // inti
    {
        int width = HexArray2Num(data + 1, 2);
        int height = HexArray2Num(data + 3, 2);
        int color = data[5];
        PRINT_DEBUG("width,height,color:%d,%d,%d\n", width, height, color);
        // PRINT_DEBUG("display_buffer_size:%d,%d\n", display_buffer_size, width * height / 8);
        // display_buffer_size = EPD_1IN54_HEIGHT * EPD_1IN54_WIDTH / 8;
        display_buffer_size = EPD_HEIGHT * EPD_WIDTH / 8;
        if (display_buffer_size != (width * height / 8))
        {
            return_log = "width or height error!";
            PRINT_ERROR("%s\n", return_log.c_str());
            return;
        }
        if (color != EPD_COLOR)
        {
            return_log = "color error!";
            PRINT_ERROR("%s\n", return_log.c_str());
            return;
        }
        // if (image_buffer != NULL)
        // {
        //     free(image_buffer);
        //     image_buffer = NULL;
        // }
        // image_buffer = (uint8_t *)malloc(display_buffer_size);
        // PRINT_INFO("imagecolor_address:%x\n", image_buffer);
        // memset(image_buffer, 0xFF, display_buffer_size);
        image_length = 0;
        image_total_length = 0;
        image_checknum = 0;
        epd_write_flag = 1;
        return_log = "inti ok";
        PRINT_DEBUG("%s\n", return_log.c_str());
        break;
    }
    case 0x2A: // data
    {
        imagecolor = data[1];
        uint16_t image_data_size = HexArray2Num(data + 2, 2);
        PRINT_DEBUG("imagecolor,image_data_size:%d,%d\n", imagecolor, image_data_size);
        PRINT_DEBUG("image_length:%d\n", image_length);
        // for (int i = 0; i < data_length - 4; i++)
        // {
        //     PRINT_RAW("%02x ", data[i + 4]);
        // }
        if (image_data_size == data_length - 4)
        {
            if (imagecolor == 0xA0)
            // if(1)
            {
                imagecolor = 0;
                PRINT_DEBUG("image_length:%d;(%d)\n", image_length, millis());
                // image_length += run_length_decoding(data + 4, image_data_size);
                // image_length += run_length_decoding(data + 4, image_data_size);
                uint32_t data_length = run_length_decoding(data + 4, image_data_size, imagecolor);
                if (image_length + data_length <= display_buffer_size)
                {
                    image_length += data_length;
                    image_total_length += data_length;
                    PRINT_INFO("image_length:%d\n", image_length);
                    PRINT_INFO("time:%d\n", millis());
                    digitalToggle(LED0);

                    if (image_length == display_buffer_size)
                    {
                        if (imagecolor == 0x00)
                        {
                            image_length = 0;
                        }
                    }
                }
                else
                {
                    return_log = "image data exceed!";
                    PRINT_ERROR("%s\n", return_log.c_str());
                }
            }

        }
        else
        {
            return_log = "image data size error!";
            PRINT_ERROR("%s\n", return_log.c_str());
        }
        break;
    }

    case 0x2F: // end
    {
        uint32_t totalsize = HexArray2Num(data + 1, 3);
        uint8_t check_num = HexArray2Num(data + 4, 1);
        uint8_t image_checknum_black = checksum(image_buffer, display_buffer_size);
        uint8_t image_checknum = (image_checknum_black) & (0xFF);
        PRINT_INFO("totalsize:%d;check_num:%d\n", totalsize, check_num);
        PRINT_INFO("image_size:%d;image_checknum:%d\n", image_total_length, image_checknum);
        // PRINT_DEBUG("%d\n", totalsize == image_length && check_num == image_checknum);

        digitalWrite(LED0, LOW);
        // if (totalsize == image_length && check_num == image_checknum)
        if (totalsize == image_total_length)
        // if (1)
        {

            PRINT_DEBUG("check ok!\n");
            // EPD_1IN54_Init(EPD_1IN54_FULL);
            display_flag = 1;
            image_length = 0;
            image_total_length = 0;
            image_checknum = 0;
            // EPD_1IN54_Display(image_buffer_black);

            // delay(100);
            // EPD_1IN54_Sleep();
            // delay(10);
            // free(image_buffer_black);
            // image_buffer_black = NULL;
        }
        else
        {
            return_log = "check error!";
            PRINT_ERROR("%s\n", return_log.c_str());
            if (0)
            {
                for (int i = 0; i < 1000; i++)
                {
                    // PRINT_RAW("(%d,%d),", i,image_buffer[i]);
                    PRINT_RAW("%d,", image_buffer[i]);
                }
            }
        }

        break;
    }
#ifdef VERSION3
#if defined(GREY_SUPPORT)
    case 0x22: // grey_inti
    {
        int width = HexArray2Num(data + 1, 2);
        int height = HexArray2Num(data + 3, 2);
        greyscale = data[5];
        PRINT_DEBUG("width,height,color:%d,%d,%d\n", width, height, greyscale);
        // PRINT_DEBUG("display_buffer_size:%d,%d\n", display_buffer_size, width * height / 8);
        int piex_data_size;
        if (greyscale == 4)
            piex_data_size = 2;
        else if (greyscale == 16)
            piex_data_size = 4;
        display_buffer_size = EPD_HEIGHT * EPD_WIDTH / 8 * piex_data_size;
        if (display_buffer_size != (width * height / 8 * piex_data_size))
        {
            return_log = "width or height error!";
            PRINT_ERROR("%s\n", return_log.c_str());
            return;
        }
        // if (color != EPD_COLOR)
        // {
        //     return_log = "color error!";
        //     PRINT_ERROR("%s\n", return_log.c_str());
        //     return;
        // }
        if (image_buffer != NULL)
        {
            free(image_buffer);
            image_buffer = NULL;
        }
        image_buffer = (uint8_t *)malloc(display_buffer_size);
        memset(image_buffer, 0xFF, display_buffer_size);
        image_length = 0;
        epd_write_flag = 0;
        return_log = "inti ok";
        PRINT_DEBUG("%s\n", return_log.c_str());
        break;
    }
    case 0x23: // grey_data
    {
        imagecolor = data[1];
        uint16_t image_data_size = HexArray2Num(data + 2, 2);
        PRINT_DEBUG("imagecolor,image_data_size:%d,%d\n", imagecolor, image_data_size);
        // PRINT_DEBUG("imagecolor:%d\n", imagecolor);
        if (image_data_size == data_length - 4)
        {
            // for (int i = 0; i < image_data_size; i++)
            // {
            //     PRINT_RAW("%02x ", data[i + 4]);
            // }

            if (1) //
            {
                // if (image_length + image_data_size <= display_buffer_size)
                // {
                // memccpy(image_buffer_black + image_length, data_buffer, '\0', size);
                if (imagecolor == 0xA0)
                {
                    // image_length += run_length_decoding(data + 4, image_data_size);
                    image_length += run_length_decoding(data + 4, image_data_size);
                    PRINT_DEBUG("image_length:%d\n", image_length);
                    digitalToggle(LED0);
                }
                else
                {
                    if (image_length + image_data_size <= display_buffer_size)
                    {
                        for (int i = 0; i < image_data_size; i++)
                        {
                            image_buffer[image_length + i] = data[i + 4];
                        }
                        image_length += image_data_size;
                        PRINT_DEBUG("image_length:%d\n", image_length);
                        digitalToggle(LED0);
                    }
                    else
                    {
                        return_log = "image data exceed!";
                        PRINT_ERROR("%s\n", return_log.c_str());
                    }
                    // if (image_length == 0)
                    // if (0)
                    // {
                    //     for (int i = 0; i < 100; i++)
                    //     {
                    //         PRINT_RAW("%02x ", image_buffer[i]);
                    //     }
                    //     // Serial.printf("%d:  %d", image_length, checksum(data_buffer, data_buffer_size));
                    //     PRINT_RAW("\n");
                    // }
                }
            }
        }
        else
        {
            return_log = "image data size error!";
            PRINT_ERROR("%s\n", return_log.c_str());
        }
        break;
    }
    case 0x24: // grey_end
    {
        uint32_t totalsize = HexArray2Num(data + 1, 3);
        uint8_t check_num = HexArray2Num(data + 4, 1);
        uint8_t image_checknum_black = checksum(image_buffer, display_buffer_size);
        uint8_t image_checknum = (image_checknum_black) & (0xFF);
        PRINT_DEBUG("totalsize:%d;check_num:%d\n", totalsize, check_num);
        PRINT_DEBUG("image_size:%d;image_checknum:%d\n", image_length, image_checknum);
        // PRINT_DEBUG("%d\n", totalsize == image_length && check_num == image_checknum);
        digitalWrite(LED0, LOW);

        // if (1)
        // {
        //     for (int k = 0;k < 200;k++)
        //     {
        //         if(k==99||k==199)
        //         {
        //         PRINT_DEBUG("k:%d\n", k);
        //         for (int i = k*100; i < (k+1)*100; i++)
        //         {
        //             // PRINT_RAW("%02x,", image_buffer[i]);
        //             PRINT_RAW("%d,", image_buffer[i]);
        //         }
        //         // Serial.printf("%d:  %d", image_length, checksum(data_buffer, data_buffer_size));
        //         PRINT_RAW("\n");
        //         delay(20);
        //         }
        //     }
        // }

        if (totalsize == image_length && check_num == image_checknum)
        // if (totalsize == image_length)
        // if (1)
        {

            PRINT_DEBUG("check ok!\n");

            display_flag = 2; // grey
            image_length = 0;
        }
        else
        {
            return_log = "check error!";
            PRINT_ERROR("%s\n", return_log.c_str());
        }

        break;
    }
#endif // GREY_SUPPORT
#endif

#elif EPD_COLOR == 3
    case 0x20: // inti
    {
        int width = HexArray2Num(data + 1, 2);
        int height = HexArray2Num(data + 3, 2);
        int color = data[5];
        PRINT_DEBUG("width,height,color:%d,%d,%d\n", width, height, color);
        // PRINT_DEBUG("display_buffer_size:%d,%d\n", display_buffer_size, width * height / 8);
        display_buffer_size = EPD_HEIGHT * EPD_WIDTH / 8;
        if (display_buffer_size != (width * height / 8))
        {
            return_log = "width or height error!";
            PRINT_ERROR("%s\n", return_log.c_str());
            return;
        }
        if (color != EPD_COLOR)
        {
            return_log = "color error!";
            PRINT_ERROR("%s\n", return_log.c_str());
            return;
        }
        // if (image_buffer != NULL)
        // {
        //     free(image_buffer);
        //     image_buffer = NULL;
        // }
#if 0
        // image_buffer = (uint8_t *)malloc(display_buffer_size * 2);
        // memset(image_buffer, 0x00, display_buffer_size * 2);
        image_buffer = (uint8_t *)malloc(display_buffer_size * 1);
        // image_buffer = (uint8_t *)malloc(4400);
        PRINT_INFO("image_buffer address:%d\n", image_buffer);


        memset(image_buffer, 0xFF, display_buffer_size * 1);
#endif
        // eink_inti();
        image_length = 0;
        image_total_length = 0;
        image_checknum = 0;
        epd_write_flag = 1;
        return_log = "inti ok";
        PRINT_DEBUG("%s\n", return_log.c_str());
        break;
    }
    case 0x2A: // data
    {
        // PRINT_INFO("checksum,,,:%x....\n",image_checknum);
        imagecolor = data[1];
        uint16_t image_data_size = HexArray2Num(data + 2, 2);
        PRINT_INFO("imagecolor,image_data_size:%d,%d\n", imagecolor, image_data_size);
        if (imagecolor == 0xA0)
        {
            imagecolor = 0;
        }
        else if (imagecolor == 0xA1)
        {
            imagecolor = 1;
        }
        PRINT_DEBUG("image_length:%d;(%d)\n", image_length, millis());
        // for (int i = 0; i < data_length - 4; i++)
        // {
        //     PRINT_RAW("%02x ", data[i + 4]);
        // }
        if (image_data_size == data_length - 4)
        {
            if (imagecolor == 0x00 || imagecolor == 0x01) // black,0;red,1;
            // if(1)
            {
                uint32_t data_length = run_length_decoding(data + 4, image_data_size, imagecolor);
#if 0
                uint32_t data_length = run_length_decoding(data + 4, 0, image_data_size);
#endif
                // if (image_length + data_length <= display_buffer_size * 2)
                if (image_length + data_length <= display_buffer_size)
                {
#if 0
                    if (image_length == 0)
                    {
                     for (int i = 0; i < image_data_size; i++)
                        {
                            PRINT_RAW("%02x ", image_buffer[i]);
                        }
                        PRINT_RAW("\n");
                    }
#endif
                    // epd_data_write(imagecolor, epd_temp_buffer, image_length, data_length);
                    // image_checknum += checksum(epd_temp_buffer, data_length);
                    image_length += data_length;
                    image_total_length += data_length;
                    PRINT_INFO("image_length:%d\n", image_length);
                    // PRINT_INFO("image_total_length:%d\n", image_total_length);
                    PRINT_INFO("time:%d\n", millis());
                    digitalToggle(LED0);

                    // PRINT_INFO("checksum2:%x....\n",image_checknum);

                    if (image_length == display_buffer_size)
                    {
                        if (imagecolor == 0x00)
                        {
                            image_length = 0;
#if 0
                            PRINT_INFO("000:%d\n", millis());
                            // PRINT_INFO("...:%d\n", millis());
                            epd_data_write(0, image_buffer, 0, display_buffer_size);
                            // PRINT_INFO("...:%d\n", millis());
                            image_checknum = checksum(image_buffer, display_buffer_size);
                            memset(image_buffer, 0x00, display_buffer_size * 1);
                            PRINT_INFO("111:%d\n", millis());
#endif
                        }
                    }
                }
                else
                {
                    return_log = "image data exceed!";
                    PRINT_ERROR("%s\n", return_log.c_str());
                }
            }
        }
        else
        {
            return_log = "image data size error!";
            PRINT_ERROR("%s\n", return_log.c_str());
        }
        break;
    }
    case 0x2F: // end
    {
        PRINT_INFO("checksum:%x....\n", image_checknum);
        uint32_t totalsize = HexArray2Num(data + 1, 3);
        uint8_t check_num = HexArray2Num(data + 4, 1);
        // uint8_t image_checknum_black = checksum(image_buffer, display_buffer_size * 2);
        // image_checknum = (image_checknum_black) & (0xFF);
#if 0
        uint8_t image_checknum_temp = checksum(image_buffer, display_buffer_size);
        image_checknum = (image_checknum + image_checknum_temp) & (0xFF);
#endif
        PRINT_INFO("totalsize:%d;check_num:%d\n", totalsize, check_num);
        PRINT_INFO("image_size:%d;image_checknum:%d\n", image_total_length, image_checknum);

        digitalWrite(LED0, LOW);
        // if ((totalsize == image_total_length || totalsize == image_total_length * 2) && check_num == image_checknum)
        if (totalsize == image_total_length)
        // if (1)
        {

            // if (totalsize == image_total_length * 2 )
            // {
            //     uint8_t data[EPD_WIDTH/8];
            //     memset(data,0x00,sizeof(data));
            //     for (int i = 0; i < EPD_HEIGHT; i++)
            //     {
            //         epd_data_write( 0x01, data, 0, EPD_WIDTH/8);
            //     }
            // }
            PRINT_DEBUG("check ok!\n");
            display_flag = 3;
            image_length = 0;
            image_total_length = 0;
            image_checknum = 0;
            // eink_inti();
            // EPD_1IN54B_Z91_Data_Write(0, image_buffer, 0, 2888);
            // EPD_1IN54B_Z91_Data_Write(1, image_buffer + 2888, 0, 2888);
#if 0
            epd_data_write(1, image_buffer, 0, display_buffer_size);
#endif
            // EPD_1IN54B_Z91_TurnOnDisplay();
            // EPD_1IN54B_Z91_Display(image_buffer,image_buffer+2888);
        }
        else
        {
            return_log = "check error!";
            PRINT_ERROR("%s\n", return_log.c_str());
            if (0)
            {
                for (int i = 0; i < 1000; i++)
                {
                    // PRINT_RAW("(%d,%d),", i,image_buffer[i]);
                    PRINT_RAW("%d,", image_buffer[i]);
                }
            }
        }

        break;
    }

#if defined(GREY_SUPPORT)
    case 0x22: // grey_inti
    {
        int width = HexArray2Num(data + 1, 2);
        int height = HexArray2Num(data + 3, 2);
        greyscale = data[5];
        PRINT_DEBUG("width,height,color:%d,%d,%d\n", width, height, greyscale);
        // PRINT_DEBUG("display_buffer_size:%d,%d\n", display_buffer_size, width * height / 8);
        int piex_data_size;
        // if (greyscale == 4)
        //     piex_data_size = 2;
        // else if (greyscale == 8)
        if (greyscale == 8)
            piex_data_size = 4;
        // else if (greyscale == 16)
        //     piex_data_size = 4;
        display_buffer_size = EPD_HEIGHT * EPD_WIDTH / 8 * piex_data_size;
        if (display_buffer_size != (width * height / 8 * piex_data_size))
        {
            return_log = "width or height error!";
            PRINT_ERROR("%s\n", return_log.c_str());
            return;
        }
        // if (color != EPD_COLOR)
        // {
        //     return_log = "color error!";
        //     PRINT_ERROR("%s\n", return_log.c_str());
        //     return;
        // }
        if (image_buffer != NULL)
        {
            free(image_buffer);
            image_buffer = NULL;
        }
        image_buffer = (uint8_t *)malloc(display_buffer_size);
        memset(image_buffer, 0x00, display_buffer_size); ////?????
        PRINT_INFO("image_buffer address:%d\n", image_buffer);

        // if (image_red_buffer != NULL)
        // {
        //     free(image_red_buffer);
        //     image_red_buffer = NULL;
        // }
        // image_red_buffer = (uint8_t *)malloc(display_buffer_size);
        // memset(image_red_buffer, 0x00, display_buffer_size);
        // PRINT_INFO("image_red_buffer address:%d\n", image_red_buffer);

        image_length = 0;
        epd_write_flag = 0;
        return_log = "inti ok";
        PRINT_DEBUG("%s\n", return_log.c_str());
        break;
    }
    case 0x23: // grey_data
    {
        imagecolor = data[1];
        uint16_t image_data_size = HexArray2Num(data + 2, 2);
        PRINT_DEBUG("imagecolor,image_data_size:%d,%d\n", imagecolor, image_data_size);
        // PRINT_DEBUG("imagecolor:%d\n", imagecolor);
        if (image_data_size == data_length - 4)
        {

            if (1) //
            {
                // if (image_length + image_data_size <= display_buffer_size)
                // {
                // memccpy(image_buffer_black + image_length, data_buffer, '\0', size);
                // if (imagecolor == 0xA0)
                // {
                //     imagecolor = 0;
                // }
                // else if (imagecolor == 0xA1)
                // {
                //     imagecolor = 1;
                // }
                // if (imagecolor == 0 || imagecolor == 1)
                if (imagecolor == 0xA0)
                {
                    // image_length += run_length_decoding(data + 4, image_data_size);
                    image_length += run_length_decoding(data + 4, image_data_size, 0);
                    PRINT_DEBUG("image_length:%d\n", image_length);
                    digitalToggle(LED0);
                    if (image_length == display_buffer_size)
                    {
                        image_total_length += image_length;
                        image_length = 0;
                    }
                }
                // else if (imagecolor == 0xA1)
                // {
                //     // image_length += run_length_decoding(data + 4, image_data_size);
                //     image_length += run_length_decoding(data + 4, 0, image_data_size, 1);
                //     PRINT_DEBUG("imager_red_length:%d\n", image_length);
                //     digitalToggle(LED0);
                //     if (image_length == display_buffer_size)
                //     {
                //         image_total_length += image_length;
                //         image_length = 0;
                //     }
                // }
            }
        }
        else
        {
            return_log = "image data size error!";
            PRINT_ERROR("%s\n", return_log.c_str());
        }
        break;
    }
    case 0x24: // grey_end
    {
        uint32_t totalsize = HexArray2Num(data + 1, 3);
        uint8_t check_num = HexArray2Num(data + 4, 1);
        uint8_t image_checknum_black = checksum(image_buffer, display_buffer_size);
        uint8_t image_checknum = (image_checknum_black) & (0xFF);
        PRINT_DEBUG("totalsize:%d;check_num:%d\n", totalsize, check_num);
        // PRINT_DEBUG("image_size:%d;image_checknum:%d\n", image_length, image_checknum);
        PRINT_DEBUG("image_size:%d;image_checknum:%d\n", image_total_length, image_checknum);
        // PRINT_DEBUG("%d\n", totalsize == image_length && check_num == image_checknum);
        digitalWrite(LED0, LOW);

        // if (1)
        // {
        //     for (int k = 0;k < 200;k++)
        //     {
        //         if(k==99||k==199)
        //         {
        //         PRINT_DEBUG("k:%d\n", k);
        //         for (int i = k*100; i < (k+1)*100; i++)
        //         {
        //             // PRINT_RAW("%02x,", image_buffer[i]);
        //             PRINT_RAW("%d,", image_buffer[i]);
        //         }
        //         // Serial.printf("%d:  %d", image_length, checksum(data_buffer, data_buffer_size));
        //         PRINT_RAW("\n");
        //         delay(20);
        //         }
        //     }
        // }

        // if (totalsize == image_total_length )
        if (totalsize == image_total_length && check_num == image_checknum)
        // if (totalsize == image_length * 2 && check_num == image_checknum)
        // if (totalsize == image_length)
        // if (1)
        {

            PRINT_DEBUG("check ok!\n");

            display_flag = 4; // grey_bwr
            image_length = 0;
        }
        else
        {
            return_log = "check error!";
            PRINT_ERROR("%s\n", return_log.c_str());
        }

        break;
    }

#endif // GREY_SUPPORT

#endif

    default:
        PRINT_ERROR("cmd error!!!\n");
    }
}

void eink_sleep(void)
{

#if defined(EPD154C1)
    EPD_1IN54_Grey_Sleep();
#elif defined(EPD154A05)
    EPD_1IN54_A05_Sleep();
#endif
}

void eink_display(uint8_t *image_black_buffer, uint8_t *image_red_buffer)
{

#if defined(EPD154C1)
    // EPD_1IN54_Display(image_buffer);
    if (image_black_buffer == NULL)
    {
        // EPD_1IN54_Grey_Display(image_buffer);
        epd_data_write(0, image_buffer, 0, EPD_HEIGHT * EPD_WIDTH / 8);
        // HAL_Delay(100);
        eink_TurnOnDisplay();
    }
    else
        EPD_1IN54_Grey_Display(image_black_buffer);
#elif defined(EPD154A05)

    if (image_black_buffer == NULL)
    {
        epd_data_write(0, image_buffer, 0, EPD_HEIGHT * EPD_WIDTH / 8);
        eink_TurnOnDisplay();
    }
    else
        EPD_1IN54_A05_Display(image_black_buffer);
#elif defined(EPD270T91)

    if (image_black_buffer == NULL)
    {
        epd_data_write(0, image_buffer, 0, EPD_HEIGHT * EPD_WIDTH / 8);
        eink_TurnOnDisplay();
    }
    else
        EPD_2IN7_T91_Display(image_black_buffer);
#endif
    // eink_sleep();

    // delay(100);
    // EPD_1IN54_Sleep();
    // delay(10);

    // if (image_buffer != NULL)
    // {
    //     free(image_buffer);
    //     image_buffer = NULL;
    // }
}

void eink_clear(void)
{

#if defined(EPD154C1)
    // EPD_1IN54_Grey_Display(image_buffer);
    // EPD_1IN54_Grey_Display(image_buffer_temp);
    EPD_1IN54_Grey_Clear();
#elif defined(EPD290Z94)
    EPD_2IN9B_Z94_Grey_Clear();
#elif defined(EPD266Z90)
    EPD_2IN66B_Z90_Grey_Clear();
#elif defined(EPD420Z99)
    EPD_4IN2B_Z99_Clear();
#elif defined(EPD583Z83)
    EPD_5IN83B_Z83_Clear();
#elif defined(EPD266H850)
    EPD_2IN66B_H850_Grey_Clear();
#elif defined(EPD154A05)
    EPD_1IN54_A05_Clear();
#endif
}

void eink_TurnOnDisplay(uint8_t part)
{

#if defined(EPD154C1)
    // EPD_1IN54_Grey_Display(image_buffer);
    EPD_1IN54_Grey_TurnOnDisplay();
#elif defined(EPD290Z94)
    EPD_2IN9B_Z94_Grey_TurnOnDisplay(part);
// EPD_2IN9B_Z94_TurnOnDisplay();
#elif defined(EPD266Z90)
    EPD_2IN66B_Z90_Grey_TurnOnDisplay(part);
#elif defined(EPD154Z91)
    // EPD_1IN54B_Z91_Display(image_buffer, image_buffer + 2888);
    EPD_1IN54B_Z91_TurnOnDisplay();
#elif defined(EPD154Z17)
    EPD_1IN54B_Z17_TurnOnDisplay();
#elif defined(EPD420Z99)
    EPD_4IN2B_Z99_TurnOnDisplay(part);
#elif defined(EPD583Z83)
    EPD_5IN83B_Z83_TurnOnDisplay();
#elif defined(EPD266H850)
    EPD_2IN66B_H850_Grey_TurnOnDisplay(part);
#elif defined(EPD154A05)
    EPD_1IN54_A05_TurnOnDisplay();
#elif defined(EPD270T91)
    EPD_2IN7_T91_TurnOnDisplay();
#endif
}

void eink_setDepth(uint8_t i)
{

#if defined(EPD154C1)
    EPD_1IN54_Grey_setDepth(i);
#elif defined(EPD290Z94)
    EPD_2IN9B_Z94_Grey_setDepth(i);
#elif defined(EPD266Z90)
    EPD_2IN66B_Z90_Grey_setDepth(i);
#elif defined(EPD420Z99)
    EPD_4IN2B_Z99_setDepth(i);
#elif defined(EPD583Z83)
    EPD_5IN83B_Z83_setDepth(i);
#elif defined(EPD266H850)
    EPD_2IN66B_H850_Grey_setDepth(i);
#endif
}

void eink_image_length_reset(void)
{
    image_length = 0;
    image_total_length = 0;
}

// void eink_grey_inti(void)
// {
//     // display_buffer_size = EPD_1IN54_HEIGHT * EPD_1IN54_WIDTH / 8*;
//     // DEV_Module_Init();
//     PRINT_DEBUG("e-Paper Init and Clear...\r\n");
//     // delay(200);
//     EPD_1IN54_Grey_fullpart(EPD_1IN54_Grey_FULL);
//     HAL_Delay(100);
//     // EPD_1IN54_Grey_Clear();
//     if (image_buffer_temp != NULL)
//     {
//         free(image_buffer_temp);
//         image_buffer_temp = NULL;
//     }
//     image_buffer_temp = (uint8_t *)malloc(EPD_HEIGHT * EPD_WIDTH / 8);
//     memset(image_buffer_temp, 0x00, EPD_HEIGHT * EPD_WIDTH / 8);
// }

void eink_grey_data_inti(void)
{

    // for (int i = 0; i < 100; i++)
    // {
    //     PRINT_RAW("%02x ", image_red_buffer[i]);
    //     // PRINT_RAW("%02x ", image_red_buffer[i + 1]);
    // }
    // PRINT_DEBUG("\n ");
#if EPD_COLOR == 3
    if (image_buffer_temp != NULL)
    {
        free(image_buffer_temp);
        image_buffer_temp = NULL;
    }
    image_buffer_temp = (uint8_t *)malloc(image_buffer_temp_size);
    memset(image_buffer_temp, 0x00, image_buffer_temp_size);
#else
    image_buffer_temp = (uint8_t *)malloc(EPD_HEIGHT * EPD_WIDTH / 8);
    memset(image_buffer_temp, 0xFF, EPD_HEIGHT * EPD_WIDTH / 8);
#endif

#if 0
    if (image_buffer_temp != NULL)
    {
        free(image_buffer_temp);
        image_buffer_temp = NULL;
    }
    image_buffer_temp = (uint8_t *)malloc(EPD_HEIGHT * EPD_WIDTH / 8);
    memset(image_buffer_temp, 0x00, EPD_HEIGHT * EPD_WIDTH / 8);

#if EPD_COLOR == 3
    if (image_red_buffer_temp != NULL)
    {
        free(image_red_buffer_temp);
        image_red_buffer_temp = NULL;
    }
    image_red_buffer_temp = (uint8_t *)malloc(EPD_HEIGHT * EPD_WIDTH / 8);
    memset(image_red_buffer_temp, 0x00, EPD_HEIGHT * EPD_WIDTH / 8);
#endif
#endif
}

int grey4_depth[4] = {0, 5, 10, 15};

int piex_comapre(int n, int min, int max) // n∈[min,max),return 0
{
    return (((n >= min) && (n < max)) ? 0 : 1);
}

bool eink_grey_display(int depth)
{
    // if(depth>0)
    bool grey_display_flag = 1;
    if (1)
    {
        PRINT_DEBUG("display_buffer_size:%d\r\n", display_buffer_size);
        PRINT_DEBUG("image_buffer_temp_size:%d\r\n", sizeof(image_buffer_temp));
        // PRINT_DEBUG("image_buffer_temp_size:%d\r\n",EPD_1IN54_HEIGHT * EPD_1IN54_WIDTH / 8);
        int j = 0;
        int temp[8];
        if (depth == 0)
        {
            memset(image_buffer_temp, 0xFF, EPD_HEIGHT * EPD_WIDTH / 8);
            grey_display_flag = 1;
        }
        else
        {
            memset(image_buffer_temp, 0x00, EPD_HEIGHT * EPD_WIDTH / 8);
            int step;
            if (greyscale == 4)
                step = 2;
            else if (greyscale == 16)
                step = 4;

            for (int i = 0; i < display_buffer_size; i = i + step)
            {
                if (greyscale == 4)
                {
                    temp[0] = piex_comapre(image_buffer[i] >> 6, greyscale - depth - 1, greyscale - 1);
                    temp[1] = piex_comapre((image_buffer[i] & 0x3F) >> 4, greyscale - depth - 1, greyscale - 1);
                    temp[2] = piex_comapre((image_buffer[i] & 0x0F) >> 2, greyscale - depth - 1, greyscale - 1);
                    temp[3] = piex_comapre(image_buffer[i] & 0x03, greyscale - depth - 1, greyscale - 1);
                    temp[4] = piex_comapre(image_buffer[i + 1] >> 6, greyscale - depth - 1, greyscale - 1);
                    temp[5] = piex_comapre((image_buffer[i + 1] & 0x3F) >> 4, greyscale - depth - 1, greyscale - 1);
                    temp[6] = piex_comapre((image_buffer[i + 1] & 0x0F) >> 2, greyscale - depth - 1, greyscale - 1);
                    temp[7] = piex_comapre(image_buffer[i + 1] & 0x03, greyscale - depth - 1, greyscale - 1);
                }
                else if (greyscale == 16)
                {
                    temp[0] = piex_comapre(image_buffer[i] >> 4, greyscale - depth - 1, greyscale - 1);
                    temp[1] = piex_comapre(image_buffer[i] & 0x0F, greyscale - depth - 1, greyscale - 1);
                    temp[2] = piex_comapre(image_buffer[i + 1] >> 4, greyscale - depth - 1, greyscale - 1);
                    temp[3] = piex_comapre(image_buffer[i + 1] & 0x0F, greyscale - depth - 1, greyscale - 1);
                    temp[4] = piex_comapre(image_buffer[i + 2] >> 4, greyscale - depth - 1, greyscale - 1);
                    temp[5] = piex_comapre(image_buffer[i + 2] & 0x0F, greyscale - depth - 1, greyscale - 1);
                    temp[6] = piex_comapre(image_buffer[i + 3] >> 4, greyscale - depth - 1, greyscale - 1);
                    temp[7] = piex_comapre(image_buffer[i + 3] & 0x0F, greyscale - depth - 1, greyscale - 1);
                }
                for (int k = 0; k < 8; k++)
                {
                    image_buffer_temp[j] += (temp[k] << (8 - k - 1));
                }

                uint8_t display_temp_data = 0;
                {
                    if (greyscale == 4)
                    {
                        temp[0] = image_buffer[i] >> 6 == greyscale - depth - 1 ? 0 : 1;
                        temp[1] = (image_buffer[i] & 0x3F) >> 4 == greyscale - depth - 1 ? 0 : 1;
                        temp[2] = (image_buffer[i] & 0x0F) >> 2 == greyscale - depth - 1 ? 0 : 1;
                        temp[3] = image_buffer[i] & 0x03 == greyscale - depth - 1 ? 0 : 1;
                        temp[4] = image_buffer[i + 1] >> 6 == greyscale - depth - 1 ? 0 : 1;
                        temp[5] = (image_buffer[i + 1] & 0x3F) >> 4 == greyscale - depth - 1 ? 0 : 1;
                        temp[6] = (image_buffer[i + 1] & 0x0F) >> 2 == greyscale - depth - 1 ? 0 : 1;
                        temp[7] = image_buffer[i + 1] & 0x03 == greyscale - depth - 1 ? 0 : 1;
                    }
                    else if (greyscale == 16)
                    {
                        temp[0] = image_buffer[i] >> 4 == greyscale - depth - 1 ? 0 : 1;
                        temp[1] = image_buffer[i] & 0x0F == greyscale - depth - 1 ? 0 : 1;
                        temp[2] = image_buffer[i + 1] >> 4 == greyscale - depth - 1 ? 0 : 1;
                        temp[3] = image_buffer[i + 1] & 0x0F == greyscale - depth - 1 ? 0 : 1;
                        temp[4] = image_buffer[i + 2] >> 4 == greyscale - depth - 1 ? 0 : 1;
                        temp[5] = image_buffer[i + 2] & 0x0F == greyscale - depth - 1 ? 0 : 1;
                        temp[6] = image_buffer[i + 3] >> 4 == greyscale - depth - 1 ? 0 : 1;
                        temp[7] = image_buffer[i + 3] & 0x0F == greyscale - depth - 1 ? 0 : 1;
                    }
                    for (int k = 0; k < 8; k++)
                    {
                        display_temp_data += (temp[k] << (8 - k - 1));
                    }
                }
                if ((!grey_display_flag) && (display_temp_data != 0xFF))
                {
                    grey_display_flag = 1;
                    PRINT_DEBUG("%d,%d...\r\n", j, display_temp_data);
                    PRINT_DEBUG("%d,%d...\r\n", image_buffer[i], image_buffer[i + 1]);
                }

                j++;
                if (j == EPD_HEIGHT * EPD_WIDTH / 8)
                {
                    PRINT_DEBUG("%d...\r\n", j);
                    break;
                }
            }
        }
    }
    int depth_temp;
    if (greyscale == 4)
        depth_temp = grey4_depth[depth];
    else if (greyscale == 16)
        depth_temp = depth;

    if (grey_display_flag)
    {

        if (depth_temp)
            eink_setDepth(depth_temp);
        eink_display(image_buffer_temp);
        PRINT_DEBUG("Display grey %d...\r\n", depth_temp);
        return 1;
    }
    else
    {
        PRINT_DEBUG(" Grey %d no data...\r\n", depth_temp);
        return 0;
    }
}

bool eink_grey_bwr_display(int depth)
{
    // if(depth>0)
    // bool grey_display_flag = 0;

#if 1
    if (1)
    {
        PRINT_DEBUG("display_buffer_size:%d\r\n", display_buffer_size);
        PRINT_DEBUG("image_buffer_temp_size:%d\r\n", image_buffer_temp_size);
        // PRINT_DEBUG("image_buffer_temp_size:%d\r\n",EPD_1IN54_HEIGHT * EPD_1IN54_WIDTH / 8);
        int j = 0;
        uint8_t temp[8];
        uint8_t pixel_temp[8];

        {
            memset(image_buffer_temp, 0x00, image_buffer_temp_size);
            int step;
            if (greyscale == 4)
                step = 3;
            else if (greyscale == 8)
                step = 4;
            else if (greyscale == 16)
                step = 5;

            uint32_t buffer_index = 0;
            while (buffer_index < display_buffer_size)
            {
                uint32_t buffer_size = min(display_buffer_size - buffer_index, image_buffer_temp_size * step);
                // PRINT_DEBUG("buffer_size,buffer_index:%d,%d\r\n", buffer_size,buffer_index);
                for (int i = 0; i < buffer_size; i = i + step) // black
                {
                    // if (greyscale == 4)
                    // {
                    //     temp[0] = piex_comapre(image_buffer[buffer_index + i] >> 6, 0, greyscale - depth);
                    //     temp[1] = piex_comapre((image_buffer[buffer_index + i] & 0x3F) >> 4, 0, greyscale - depth);
                    //     temp[2] = piex_comapre((image_buffer[buffer_index + i] & 0x0F) >> 2, 0, greyscale - depth);
                    //     temp[3] = piex_comapre(image_buffer[buffer_index + i] & 0x03, 0, greyscale - depth);
                    //     temp[4] = piex_comapre(image_buffer[buffer_index + i + 1] >> 6, 0, greyscale - depth);
                    //     temp[5] = piex_comapre((image_buffer[buffer_index + i + 1] & 0x3F) >> 4, 0, greyscale - depth);
                    //     temp[6] = piex_comapre((image_buffer[buffer_index + i + 1] & 0x0F) >> 2, 0, greyscale - depth);
                    //     temp[7] = piex_comapre(image_buffer[buffer_index + i + 1] & 0x03, 0, greyscale - depth);
                    // }
                    // else if (greyscale == 8)
                    if (greyscale == 8)
                    {
                        temp[0] = image_buffer[buffer_index + i] >> 4;
                        temp[1] = image_buffer[buffer_index + i] & 0x0F;
                        temp[2] = image_buffer[buffer_index + i + 1] >> 4;
                        temp[3] = image_buffer[buffer_index + i + 1] & 0x0F;
                        temp[4] = image_buffer[buffer_index + i + 2] >> 4;
                        temp[5] = image_buffer[buffer_index + i + 2] & 0x0F;
                        temp[6] = image_buffer[buffer_index + i + 3] >> 4;
                        temp[7] = image_buffer[buffer_index + i + 3] & 0x0F;

                        for (int k = 0; k < 8; k++)
                        {
                            if (!(temp[k] >> 3))
                            {
                                pixel_temp[k] = piex_comapre(temp[k] & 0x07, 0, greyscale - depth);
                            }
                            else
                            {
                                pixel_temp[k] = 1;
                            }
                        }
                    }
                    for (int k = 0; k < 8; k++)
                    {
                        image_buffer_temp[j] += (pixel_temp[k] << (8 - k - 1));
                    }
                    j++;
                    // if (j == EPD_HEIGHT * EPD_WIDTH / 8)
                    // {
                    //     PRINT_DEBUG("%d...\r\n", j);
                    //     break;
                    // }
                }
                // EPD_2IN9B_Z94_Grey_Data_Write(0, image_buffer_temp, buffer_index / 2, j);
                epd_data_write(0, image_buffer_temp, buffer_index / step, j);
                // memset(image_buffer_temp, 0x00, image_buffer_temp_size);
                // EPD_2IN9B_Z94_Grey_Data_Write(1, image_buffer_temp, buffer_index / 2, j);
                memset(image_buffer_temp, 0x00, image_buffer_temp_size);
                buffer_index += buffer_size;
                j = 0;
            }
            buffer_index = 0;
            j = 0;
            while (buffer_index < display_buffer_size)
            {
                uint32_t buffer_size = min(display_buffer_size - buffer_index, image_buffer_temp_size * step);
                // PRINT_DEBUG("buffer_size,buffer_index:%d,%d\r\n", buffer_size,buffer_index);
                for (int i = 0; i < buffer_size; i = i + step) // red
                {
                    // if (greyscale == 4)
                    // {
                    //     temp[0] = 1 - piex_comapre(image_red_buffer[buffer_index + i] >> 6, depth, greyscale);
                    //     temp[1] = 1 - piex_comapre((image_red_buffer[buffer_index + i] & 0x3F) >> 4, depth, greyscale);
                    //     temp[2] = 1 - piex_comapre((image_red_buffer[buffer_index + i] & 0x0F) >> 2, depth, greyscale);
                    //     temp[3] = 1 - piex_comapre(image_red_buffer[buffer_index + i] & 0x03, depth, greyscale);
                    //     temp[4] = 1 - piex_comapre(image_red_buffer[buffer_index + i + 1] >> 6, depth, greyscale);
                    //     temp[5] = 1 - piex_comapre((image_red_buffer[buffer_index + i + 1] & 0x3F) >> 4, depth, greyscale);
                    //     temp[6] = 1 - piex_comapre((image_red_buffer[buffer_index + i + 1] & 0x0F) >> 2, depth, greyscale);
                    //     temp[7] = 1 - piex_comapre(image_red_buffer[buffer_index + i + 1] & 0x03, depth, greyscale);
                    // }
                    // else if (greyscale == 8)
                    if (greyscale == 8)
                    {
                        temp[0] = image_buffer[buffer_index + i] >> 4;
                        temp[1] = image_buffer[buffer_index + i] & 0x0F;
                        temp[2] = image_buffer[buffer_index + i + 1] >> 4;
                        temp[3] = image_buffer[buffer_index + i + 1] & 0x0F;
                        temp[4] = image_buffer[buffer_index + i + 2] >> 4;
                        temp[5] = image_buffer[buffer_index + i + 2] & 0x0F;
                        temp[6] = image_buffer[buffer_index + i + 3] >> 4;
                        temp[7] = image_buffer[buffer_index + i + 3] & 0x0F;

                        for (int k = 0; k < 8; k++)
                        {
                            if ((temp[k] >> 3))
                            {
                                pixel_temp[k] = 1 - piex_comapre(temp[k] & 0x07, depth, greyscale);
                                // pixel_temp[k]=0;
                            }
                            else
                            {
                                pixel_temp[k] = 0;
                            }
                        }
                    }
                    for (int k = 0; k < 8; k++)
                    {
                        image_buffer_temp[j] += (pixel_temp[k] << (8 - k - 1));
                    }
                    // image_buffer_temp[j]=0;
                    j++;

                    // if (j == EPD_HEIGHT * EPD_WIDTH / 8)
                    // {
                    //     PRINT_DEBUG("%d...\r\n", j);
                    //     break;
                    // }
                }
                // EPD_2IN9B_Z94_Grey_Data_Write(1, image_buffer_temp, buffer_index / 2, j);
                epd_data_write(1, image_buffer_temp, buffer_index / step, j);
                memset(image_buffer_temp, 0x00, image_buffer_temp_size);
                buffer_index += buffer_size;
                j = 0;
            }
        }
    }

    int depth_temp;
    // if (greyscale == 4)
    depth_temp = depth;

    if (1)
    {
        eink_TurnOnDisplay(EPD_DISPLAY_PART);
        PRINT_DEBUG("Display grey %d...\r\n", depth_temp);
        return 1;
    }
#endif
}

void eink_grey_display_end(void)
{
    free(image_buffer);
    image_buffer = NULL;
    free(image_buffer_temp);
    image_buffer_temp = NULL;
}
